package com.atomcorp.controlador;

import com.atomcorp.modelo.Catalogo;
import com.atomcorp.modelo.CatalogoDetalle;
import com.atomcorp.modelo.Choice;
import com.atomcorp.servicio.CatalogoDetalleServicio;
import com.atomcorp.servicio.CatalogoServicio;
import java.net.URL;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.ResourceBundle;
import java.util.logging.Level;
import java.util.logging.Logger;
import javafx.beans.value.ChangeListener;
import javafx.beans.value.ObservableValue;
import javafx.collections.FXCollections;
import javafx.collections.ObservableList;
import javafx.event.ActionEvent;
import javafx.fxml.FXML;
import javafx.fxml.FXMLLoader;
import javafx.fxml.Initializable;
import javafx.scene.Parent;
import javafx.scene.Scene;
import javafx.scene.control.Button;
import javafx.scene.control.ChoiceBox;
import javafx.scene.control.Pagination;
import javafx.scene.control.TableColumn;
import javafx.scene.control.TableView;
import javafx.scene.control.TextField;
import javafx.scene.control.Tooltip;
import javafx.scene.control.cell.PropertyValueFactory;
import javafx.stage.Stage;
import javax.swing.JOptionPane;
import vista.SistemaFacturacion;

/**
 *
 * @author Harold
 */
public class AdministrarCatDetController implements Initializable {
    
    @FXML Button btnBuscar;
    @FXML Button btnNuevo;
    @FXML Button btnEliminar;
    @FXML Button btnCancelar;
    @FXML Button btnSeleccionar;
    @FXML TextField txtNemonico;
    @FXML TextField txtNombre;
    @FXML TextField txtDescripcion;
    @FXML ChoiceBox cbCatalogo;
    @FXML TextField txtCatDetallePadre;
    @FXML TextField txtAnio;
    @FXML TextField txtRangoMinimo;
    @FXML TextField txtRangoMaximo;
    @FXML TextField txtPorcentaje;
    @FXML TextField txtValor;
    @FXML TableView tbCatalogos;
    @FXML Pagination pagination;
    @FXML TableColumn colAnio;
    @FXML TableColumn colCatalogo;
    @FXML TableColumn colCatDetPadre;
    @FXML TableColumn colNemonico;
    @FXML TableColumn colNombre;
    @FXML TableColumn colDescripcion;
    @FXML TableColumn colRangoMinimo;
    @FXML TableColumn colRangoMaximo;
    @FXML TableColumn colPorcentaje;
    @FXML TableColumn colValor;
    private CatalogoDetalle nuevoCatalogoDetalle;
    private CatalogoServicio catalogoServicio;
    private ObservableList<CatalogoDetalle> listaCatDetTotal = FXCollections.observableArrayList();
    private ObservableList<CatalogoDetalle> resulConsulta = FXCollections.observableArrayList();
    int pageCount = 5;
    int itemsPerPage = 5;
    int currentPageIndex = 0;
    private Long txtIdCatalogoDetalle;
    private Long txtIdCatDetPadre;
    private Stage stage;
    private Long idCatalogoSeleccionado;
    private int anioSeleccionado;
    private static AdministrarCatDetController instance;
    private CatalogoDetalleServicio catalogoDetalleServicio;
    
    @Override
    public void initialize(URL url, ResourceBundle rb) {
        btnBuscar.setTooltip(new Tooltip("Buscar catálogo"));
        btnNuevo.setTooltip(new Tooltip("Guardar/Editar catálogo"));
        btnEliminar.setTooltip(new Tooltip("Eliminar catálogo"));
        btnCancelar.setTooltip(new Tooltip("Cancelar/limpiar"));
        btnEliminar.setDisable(true);
        txtCatDetallePadre.setDisable(true);
        btnSeleccionar.setTooltip(new Tooltip("Seleccione el catálogo detalle"));
        catalogoServicio = new CatalogoServicio();
        catalogoDetalleServicio = new CatalogoDetalleServicio();
        idCatalogoSeleccionado = 0L;
        anioSeleccionado = 0;
        txtRangoMinimo.setText("0.0");
        txtRangoMaximo.setText("0.0");
        txtPorcentaje.setText("0.0");
        txtValor.setText("0.0");
        obtenerAnio();
        obtenerCatalogos();
        iniciarColumnasTablaCatalogosDetalle();
        listarCatDetTotal();
        seleccionarCatalogoDetalle();
        paginarTabla();
    }

    public AdministrarCatDetController() {
        instance = this;
    }
    
    public void seleccionarCatalogoDetalle(){
        tbCatalogos.getSelectionModel().selectedItemProperty().addListener(new ChangeListener<CatalogoDetalle>() {
            @Override
            public void changed(ObservableValue<? extends CatalogoDetalle> ov, CatalogoDetalle valorAnterior, CatalogoDetalle valorNuevo) { 
                if(valorNuevo != null){
                    txtIdCatalogoDetalle = valorNuevo.getId();
                    txtIdCatDetPadre = valorNuevo.getDetallePadreId();
                    mostrarDetalleCatalogo(valorNuevo);
                }                
            }
        });
    }
    
    public void paginarTabla(){
        pageCount = getPageCount(listaCatDetTotal.size(), itemsPerPage);
        pagination.setPageCount(pageCount);
        pagination.currentPageIndexProperty().addListener(new ChangeListener<Number>() {
            @Override
            public void changed(ObservableValue<? extends Number> observable, Number oldValue, Number newValue) {
              currentPageIndex = newValue.intValue();
              actualizarTablaCatalogosDetalle();
            }
        });
    }
    
    public void iniciarColumnasTablaCatalogosDetalle(){
        colAnio.setCellValueFactory(new PropertyValueFactory<CatalogoDetalle, Integer>("anio"));
        colNemonico.setCellValueFactory(new PropertyValueFactory<CatalogoDetalle, String>("nemonico"));
        colNombre.setCellValueFactory(new PropertyValueFactory<CatalogoDetalle, String>("nombre"));
        colDescripcion.setCellValueFactory(new PropertyValueFactory<CatalogoDetalle, String>("descripcion"));
        colCatalogo.setCellValueFactory(new PropertyValueFactory<CatalogoDetalle, String>("nombreCatalogo"));
        colCatDetPadre.setCellValueFactory(new PropertyValueFactory<CatalogoDetalle, String>("nombrePadre"));
        colRangoMinimo.setCellValueFactory(new PropertyValueFactory<CatalogoDetalle, Double>("rangoMinimo"));
        colRangoMaximo.setCellValueFactory(new PropertyValueFactory<CatalogoDetalle, Double>("rangoMaximo"));
        colPorcentaje.setCellValueFactory(new PropertyValueFactory<CatalogoDetalle, Double>("porcentaje"));
        colValor.setCellValueFactory(new PropertyValueFactory<CatalogoDetalle, Double>("valor"));
    }
    
    public void listarCatDetTotal(){
        mostrarDetalleCatalogo(null);
        tbCatalogos.getItems().removeAll(listaCatDetTotal);
        if(listaCatDetTotal != null){listaCatDetTotal.removeAll(listaCatDetTotal);}
        listaCatDetTotal = catalogoDetalleServicio.obtenerCatDetalleTotal(anioSeleccionado);
        if (listaCatDetTotal != null) {          
            actualizarTablaCatalogosDetalle();
        }
    }
    
    private void mostrarDetalleCatalogo(CatalogoDetalle catalogoDetalle) {
        int i = 0;
        if (catalogoDetalle != null) {
            btnEliminar.setDisable(false);
            txtAnio.setText(Integer.toString(catalogoDetalle.getAnio()));
            txtNemonico.setText(catalogoDetalle.getNemonico());
            txtNombre.setText(catalogoDetalle.getNombre());
            txtDescripcion.setText(catalogoDetalle.getDescripcion());
            for(Object c : cbCatalogo.getItems()){
                if(c != null && c.toString().trim().equals(catalogoDetalle.getNombreCatalogo().trim())){                    
                    break;
                }
                i++;
            }
            cbCatalogo.getSelectionModel().select(i);
            txtCatDetallePadre.setText(catalogoDetalle.getNombrePadre());
            txtRangoMinimo.setText(Double.toString(catalogoDetalle.getRangoMinimo()));
            txtRangoMaximo.setText(Double.toString(catalogoDetalle.getRangoMaximo()));
            txtPorcentaje.setText(Double.toString(catalogoDetalle.getPorcentaje()));
            txtValor.setText(Double.toString(catalogoDetalle.getValor()));
        } else {
            limpiarCatalogoDetalle();
        }
    }
    
    public void limpiarCatalogoDetalle() {
        nuevoCatalogoDetalle = new CatalogoDetalle();
        txtNemonico.setText("");
        txtNombre.setText("");
        txtDescripcion.setText("");
        cbCatalogo.getSelectionModel().clearSelection();
        txtCatDetallePadre.setText("");
        txtRangoMinimo.setText("0.0");
        txtRangoMaximo.setText("0.0");
        txtPorcentaje.setText("0.0");
        txtValor.setText("0.0");
        btnEliminar.setDisable(true);
        idCatalogoSeleccionado = 0L;
    }
    
    public void actualizarTablaCatalogosDetalle(){
        pageCount = getPageCount(listaCatDetTotal.size(), itemsPerPage);
        pagination.setPageCount(pageCount);
        tbCatalogos.getItems().setAll(listaCatDetTotal.subList(currentPageIndex * itemsPerPage, ((currentPageIndex * itemsPerPage + itemsPerPage <= listaCatDetTotal.size()) ? currentPageIndex * itemsPerPage + itemsPerPage : listaCatDetTotal.size())));
    }
    
    private int getPageCount(int totalCount, int itemsPerPage) {
        float floatCount = Float.valueOf(totalCount) / Float.valueOf(itemsPerPage);
        int intCount = totalCount / itemsPerPage;
        return ((floatCount > intCount) ? ++intCount : intCount);
    }
            
    public void obtenerAnio(){
        SimpleDateFormat formato = new SimpleDateFormat("yyyy");
        txtAnio.setText(formato.format(new Date()).toString());
        if(!txtAnio.getText().equals("")){
            anioSeleccionado = Integer.parseInt(txtAnio.getText());
        }
    }
    
    public void obtenerParametros(){
        Choice cat = (Choice) cbCatalogo.getSelectionModel().getSelectedItem();
        if(cat != null){
            idCatalogoSeleccionado = cat.getId();
        }
        if(!txtAnio.getText().equals("")){
            anioSeleccionado = Integer.parseInt(txtAnio.getText());
        }        
    }
    
    public void obtenerCatalogos(){
        ObservableList<Choice> choices = FXCollections.observableArrayList();
        for(Catalogo c : catalogoServicio.listarCatalogos()){
            choices.add(new Choice(c.getId(), c.getNombre()));
        }
        cbCatalogo.setItems(choices);
    }
    
    public void buscarCatalogosDetalle(){
        if(!txtNemonico.getText().equals("")){
            listarCatalogosPorCriterio("NEMONICO",txtNemonico.getText());
        }else if(!txtNombre.getText().equals("")){
            listarCatalogosPorCriterio("NOMBRE",txtNombre.getText());
        }else{
            listarCatDetTotal();
        }
    }
    
    public void listarCatalogosPorCriterio(String condicion, String valor) {
        mostrarDetalleCatalogo(null);
        tbCatalogos.getItems().removeAll(listaCatDetTotal);
        if(listaCatDetTotal != null){listaCatDetTotal.removeAll(listaCatDetTotal);}
        listaCatDetTotal = catalogoDetalleServicio.obtenerCatalogoDetallePorCriterio(condicion, valor.toUpperCase());
        if (listaCatDetTotal != null) {            
            actualizarTablaCatalogosDetalle();
        }
    }
    
    public void ingresarCatalogosDetalle(){
        resulConsulta = catalogoDetalleServicio.obtenerCatalogoDetallePorCriterio("NEMONICO", txtNemonico.getText());
        if(resulConsulta.size() == 0){
            if(txtIdCatDetPadre == null){txtIdCatDetPadre = 0L;}
            nuevoCatalogoDetalle = new CatalogoDetalle(txtNombre.getText(),txtNemonico.getText(),txtDescripcion.getText(),
                                                       txtIdCatDetPadre,idCatalogoSeleccionado,Boolean.TRUE,
                                                       Double.parseDouble(txtPorcentaje.getText()), Double.parseDouble(txtRangoMinimo.getText()),
                                                       Double.parseDouble(txtRangoMaximo.getText()),anioSeleccionado,Double.parseDouble(txtValor.getText()));
            catalogoDetalleServicio.ingresar(nuevoCatalogoDetalle);
        }else{
            obtenerParametros();
            nuevoCatalogoDetalle = new CatalogoDetalle(txtIdCatalogoDetalle,txtNombre.getText(),txtNemonico.getText(),txtDescripcion.getText(),
                                                       txtIdCatDetPadre,idCatalogoSeleccionado,Boolean.TRUE,
                                                       Double.parseDouble(txtPorcentaje.getText()), Double.parseDouble(txtRangoMinimo.getText()),
                                                       Double.parseDouble(txtRangoMaximo.getText()),anioSeleccionado,Double.parseDouble(txtValor.getText()));
            catalogoDetalleServicio.editar(nuevoCatalogoDetalle);
        }
        listarCatDetTotal();
        limpiarCatalogoDetalle();
    }
    
    public void eliminarCatalogoDetalle(){
        int confirmarEliminar = JOptionPane.showConfirmDialog(null, "Realmente desea eliminar este catálogo?");
        if (confirmarEliminar == 0) {
            boolean ok = catalogoDetalleServicio.eliminar(txtIdCatalogoDetalle);
            if(ok){
               JOptionPane.showMessageDialog(null, "Registro eliminado correctamente"); 
               listarCatDetTotal();
            }
        }
    }
    
    public void seleccionarPadre(){
        stage = new Stage();
        stage.setResizable(false);
        obtenerParametros();
        if(idCatalogoSeleccionado == 0L || anioSeleccionado == 0){
            JOptionPane.showMessageDialog(null, "Debe seleccionar el año y el catálogo");
        }else{
            iniciarArbol();
            stage.show();
        }        
    }
    
    private void iniciarArbol() {
        try {
            replacePlantalla("arbolCatalogoDetalle.fxml");
        } catch (Exception ex) {
            Logger.getLogger(AdministrarCatDetController.class.getName()).log(Level.SEVERE, null, ex);
        }
    }

    private Parent replacePlantalla(String fxml) throws Exception {
        FXMLLoader fxmlLoader = new FXMLLoader(SistemaFacturacion.class.getResource(fxml));
        Parent page = (Parent)fxmlLoader.load();
        ArbolCatDetController controller = fxmlLoader.<ArbolCatDetController>getController();
        controller.obtenerListaCatDetalle(idCatalogoSeleccionado, anioSeleccionado);
        Scene scene = stage.getScene();
        stage.setResizable(false);
        stage.setTitle("Selección de Catálogo Detalle Padre");
        if (scene == null) {
            scene = new Scene(page);
            stage.setScene(scene);
        } else {
            stage.getScene().setRoot(page);
        }
        stage.sizeToScene();
        return page;
    }
    
    public void cerrarVentana(Choice padre){
        txtIdCatDetPadre = padre.getId();
        txtCatDetallePadre.setText(padre.toString());
        stage.hide();
    }

    public static AdministrarCatDetController getInstance() {
        return instance;
    }

    public static void setInstance(AdministrarCatDetController instance) {
        AdministrarCatDetController.instance = instance;
    }

    public Long getIdCatalogoSeleccionado() {
        return idCatalogoSeleccionado;
    }

    public void setIdCatalogoSeleccionado(Long idCatalogoSeleccionado) {
        this.idCatalogoSeleccionado = idCatalogoSeleccionado;
    }

    public int getAnioSeleccionado() {
        return anioSeleccionado;
    }

    public void setAnioSeleccionado(int anioSeleccionado) {
        this.anioSeleccionado = anioSeleccionado;
    }
    
    @FXML
    protected void itemAdministrar(ActionEvent event) {
        SistemaFacturacion.getInstance().pantallaAdministracion();
    }
    
    @FXML
    protected void itemCliente(ActionEvent event) {
        SistemaFacturacion.getInstance().pantallaClientes();
    }
    
    @FXML
    protected void itemProducto(ActionEvent event) {
        SistemaFacturacion.getInstance().pantallaAdministracion();
    }
    
    @FXML
    protected void itemFactura(ActionEvent event) {
        SistemaFacturacion.getInstance().pantallaFactura();
    }
    
    @FXML
    protected void itemReporte(ActionEvent event) {
        SistemaFacturacion.getInstance().pantallaAdministracion();
    }
    
}
